﻿using System;
using System.ComponentModel;
using System.Diagnostics;
using System.Drawing.Imaging;
using System.IO;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using Mido.Domain;
using Mido.Properties;
using Mido.Utils.Mvvm;

namespace Mido.UiModules.SaveDialogModule
{
	internal class SaveDialogViewModel : ViewModelBase
	{
		private SaveDialogModel _model;
		private double _progress;
		private bool _openDestinitionFolder = true;
		private bool _createSubfolder;
		private string _folder;
		private ImageFormat _format = ImageFormat.Jpeg;

		internal SaveDialogViewModel(SaveDialogModel model)
        {
            if (model == null) 
                throw new ArgumentNullException("model");

            Model = model;
        }

		public SimpleCommand ChooseSaveFolderCommand
		{
			get { return new SimpleCommand(ChooseSaveFolder); }
		}

		public SimpleCommand SaveCommand
		{
			get { return new SimpleCommand(OnSave); }
		}

		public double Progress
		{
			get { return _progress; }
			set 
			{ 
				_progress = value;
				RaisePropertyChanged("Progress");
			}
		}

		public ImageFormat Format
		{
			get { return _format; }
			set
			{
				_format = value;
				RaisePropertyChanged("Format");
			}
		}

		private static string GetUniqueFilename(string fullPath)
		{
			if (!Path.IsPathRooted(fullPath))
				fullPath = Path.GetFullPath(fullPath);

			if (File.Exists(fullPath))
			{
				String filename = Path.GetFileName(fullPath);
				String path = fullPath.Substring(0, fullPath.Length - filename.Length);
				String filenameWOExt = Path.GetFileNameWithoutExtension(fullPath);
				String ext = Path.GetExtension(fullPath);
				int n = 1;
				do
				{
					fullPath = Path.Combine(path, String.Format("{0} ({1}){2}", filenameWOExt, (n++), ext));
				} 
				while (File.Exists(fullPath));
			}
			return fullPath;
		}

		private void OnSave()
		{			
			string dirPath = Model.DestinitionFolder;
			if (string.IsNullOrEmpty(dirPath))
			{
				MessageBox.Show(Resources.SaveDialogViewModel_OnSave_Please_specify_a_valid_path_, "Mido", MessageBoxButtons.OK);
				return;
			}

			try
			{

			
			if (CreateSubfolder)
				dirPath = Path.Combine(dirPath, DateTime.Now.ToString("yyyy-MM-dd hh-mm-ss"));

			if (!Directory.Exists(dirPath))
				Directory.CreateDirectory(dirPath);
			}
			catch (Exception)
			{
				MessageBox.Show(Resources.SaveDialogViewModel_OnSave_Cannot_create_directory__Please_specify_a_valid_path_, "Mido", MessageBoxButtons.OK);
				return;
			}

			_folder = dirPath;
			Progress = 0;

			BackgroundWorker worker = new BackgroundWorker();
			worker.DoWork += (sender, e) =>
			{
				for (int index = 0, count = Model.DomainModel.Images.Count; index < count; index++)
				{
					ProcessedImage image = Model.DomainModel.Images[index];
					string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(image.FileInfo.Name);
					if (Format == ImageFormat.Bmp)
						fileNameWithoutExtension += ".bmp";
					else if (Format == ImageFormat.Png)
						fileNameWithoutExtension += ".png";
					if (Format == ImageFormat.Jpeg)
						fileNameWithoutExtension += ".jpeg";
					if (Format == ImageFormat.Gif)
						fileNameWithoutExtension += ".gif";
					string outputPath = GetUniqueFilename(Path.Combine(dirPath, fileNameWithoutExtension));

					image.SaveWatermarkedImageTo(outputPath, Format);
					Progress = (index + 1)/Convert.ToDouble(Model.DomainModel.Images.Count)*100D;
				}
				Progress = 0;
			};

			worker.RunWorkerAsync();
			if (OpenDestinitionFolder)
				worker.RunWorkerCompleted += worker_RunWorkerCompleted;
		}

		void worker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
		{
			Process.Start(_folder);
		}

		public SaveDialogModel Model
		{
			get { return _model; }
			set { _model = value; }
		}

		public bool OpenDestinitionFolder
		{
			get { return _openDestinitionFolder; }
			set
			{
				_openDestinitionFolder = value;
				RaisePropertyChanged("OpenDestinitionFolder");
			}
		}

		public bool CreateSubfolder
		{
			get { return _createSubfolder; }
			set
			{
				_createSubfolder = value;
				RaisePropertyChanged("CreateSubfolder");
			}
		}

		private void ChooseSaveFolder()
		{
			FolderBrowserDialog dialog = new FolderBrowserDialog { ShowNewFolderButton = true };
			DialogResult result = dialog.ShowDialog();

			if (result != DialogResult.OK)
				return;

			Model.DestinitionFolder = dialog.SelectedPath;
		}
	}
}
